#include "mesh.h"

void Mesh::init() {
    // 创建顶点数组
    glGenVertexArrays(1, &vao);
    // 创建顶点缓冲对象
    glGenBuffers(1, &vbo);
    // 创建顶点缓冲对象
    glGenBuffers(1, &ebo);
    // 绑定顶点数组
    glBindVertexArray(vao);
    // 绑定顶点缓冲对象
    glBindBuffer(GL_ARRAY_BUFFER, vbo);
    // 顶点数据复制到当前绑定缓冲对象
    glBufferData(GL_ARRAY_BUFFER, vertices.size() * sizeof(Vertex), &vertices[0], GL_STATIC_DRAW);
    // 绑定顶点缓冲对象
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ebo);
    // 顶点数据复制到当前绑定缓冲对象
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, indices.size() * sizeof(unsigned int), &indices[0], GL_STATIC_DRAW);
    // 设置顶点属性指针
    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (void*)0);
    glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (void*)(offsetof(Vertex, normal)));
    glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(Vertex), (void*)(offsetof(Vertex, texCoord)));
    // 启用顶点属性 0
    glEnableVertexAttribArray(0);
    glEnableVertexAttribArray(1);
    glEnableVertexAttribArray(2);
    // 解除绑定顶点对象
    glBindBuffer(GL_ARRAY_BUFFER, 0); 
    // 解除绑定顶点数组
    glBindVertexArray(0); 
}
void Mesh::draw(unsigned int shaderProgram) {
    // glUseProgram(shaderProgram);
    unsigned int texture_diffuse = 1;
    unsigned int texture_specular = 1;
    unsigned int texture_normal = 1;
    unsigned int texture_height = 1;
    if (textures.size() == 0) {
        glActiveTexture(GL_TEXTURE0);
        setUniforn1i(shaderProgram, "texture_diffuse1", 0);
        glBindTexture(GL_TEXTURE_2D, 0);
        glActiveTexture(GL_TEXTURE0);
        setUniforn1i(shaderProgram, "texture_specular1", 0);
        glBindTexture(GL_TEXTURE_2D, 0);
    } else {
        for(int i = 0, l = textures.size(); i < l; i++){
            glActiveTexture(GL_TEXTURE0 + textures[i].id);
            char name[1024] = {0};
            if (strcmp(textures[i].type, "texture_diffuse") == 0) {
                sprintf(name, "material.texture_diffuse%d", texture_diffuse++);
            } else if (strcmp(textures[i].type, "texture_specular") == 0) {
                sprintf(name, "material.texture_specular%d", texture_specular++);
            } else if (strcmp(textures[i].type, "texture_normal") == 0) {
                sprintf(name, "material.texture_normal%d", texture_normal++);
            } else if (strcmp(textures[i].type, "texture_height") == 0) {
                sprintf(name, "material.texture_height%d", texture_height++);
            }
            // printf("Texture(id: %d, type: %s, path: %s) | name: %s\n", textures[i].id, textures[i].type, textures[i].path, name);
            setUniforn1i(shaderProgram, name, textures[i].id);
            glBindTexture(GL_TEXTURE_2D, textures[i].id);
        }
    }
    glBindVertexArray(vao);
    glDrawElements(GL_TRIANGLES, indices.size(), GL_UNSIGNED_INT, 0);
    glBindVertexArray(0);
    glActiveTexture(GL_TEXTURE0);
}